package com.qy33.service;

import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import com.qy33.entity.Dot;
import com.qy33.entity.Stock;
import com.qy33.util.DateUtil;

/**
 * 高低点计算
 * @author qy33
 * @date 2013-01-25
 */
public class DotService extends BaseService {
	
	// 计算20天内的最高、最低点
	private final int DAYS = 20;
	
	/**
	 * 得到所有高低点
	 * @param code
	 * @param list
	 * @return
	 */
	public List<Dot> getAllHighLow(String code, List<Stock> list) {
		// 为空则查所有数据
		if (list == null) {
			list = stockDao.findByCode(code);
		}
		
		List<Dot> dots = new ArrayList<Dot>();
		dots.addAll(this.getAllHigh(code, list));
		dots.addAll(this.getAllLow(code, list));
		
		Collections.sort(dots, new Comparator<Dot>() {

			@Override
			public int compare(Dot o1, Dot o2) {
				Long d1 = Long.parseLong(o1.getDate());
				Long d2 = Long.parseLong(o2.getDate());
				if (d1 < d2) {
					return -1;
				} else if (d1 > d2) {
					return 1;
				}
				return 0;
			}
		});
		
//		return (dots);
		return processRepeat(dots);
	}
	
	/**
	 * 处理点的重复情况
	 * @param dots
	 * @return
	 */
	private List<Dot> processRepeat(List<Dot> dots) {
		List<Dot> result = new ArrayList<Dot>();
		
		for (int i = 0; i < dots.size() - 1; i++) {
			Dot base = dots.get(i);
			Dot next = dots.get(i+1);
			
			if (base.getType() == next.getType()) {
				if (base.getType() == Dot.Type_High ) {
					if (base.getPrice().doubleValue() < next.getPrice().doubleValue()) {
						result.add(next);
					} else {
						result.add(base);
					}
				} else if (base.getType() == Dot.Type_Low ) {
					if (base.getPrice().doubleValue() > next.getPrice().doubleValue()) {
						result.add(next);
					} else {
						result.add(base);
					}
				}
				i++;
			} else {
				result.add(base);
			}
		}
		return result;
	}

	/**
	 * 找到所有低点
	 * @param code
	 * @param list
	 * @return
	 */
	public List<Dot> getAllLow(String code, List<Stock> list) {
		/*
		 * 低点的定义：
		 * 1. 价格最低
		 * 2. 往前#DAYS/2个周期、往后#DAYS/2个周期价格都比它高
		 */
		
		// 为空则查所有数据
		if (list == null) {
			list = stockDao.findByCode(code);
		}
		// 先放入map中, key=时间，value=stock对象
		List<Dot> result = new ArrayList<Dot>();
		Map<String, Stock> dateMap = new HashMap<String, Stock>();
		for (Stock stock : list) {
			dateMap.put(stock.getDate(), stock);
		}
		// 往前#DAYS/2天， 往后#DAYS/2天的推算
		for (Stock stock : list) {
			String date = stock.getDate();
			
			// 得到前后10天的股票对象
			List<Stock> toCompareList = new ArrayList<Stock>();
			for (int i = 1; i <= DAYS/2; i++) {
				String compareBeforeDate = DateUtil.addDays(date, i, "yyyyMMdd");
				String compareAfterDate = DateUtil.addDays(date, -i, "yyyyMMdd");
				
				Stock beforeStock = dateMap.get(compareBeforeDate);
				if (beforeStock != null) {
					toCompareList.add(beforeStock);
				}
				Stock afterStock = dateMap.get(compareAfterDate);
				if (afterStock != null) {
					toCompareList.add(afterStock);
				}
			}
			
			// 比较价格
			boolean low = true;
			for (Stock compareStock : toCompareList) {
				if (stock.getLow().doubleValue() > compareStock.getLow().doubleValue()) {
					low = false;
					break;
				}
			}
			if (low) {
				Dot dot = new Dot();
				dot.setType(Dot.Type_Low);
				dot.setCode(stock.getCode());
				dot.setPrice(stock.getLow());
				dot.setDate(stock.getDate());
				
				result.add(dot);
			}
		}
		return result;
	}
	
	/**
	 * 找到所有低点
	 * @param code
	 * @param list
	 * @return
	 */
	public List<Dot> getAllHigh(String code, List<Stock> list) {
		/*
		 * 高点的定义：
		 * 1. 价格最高
		 * 2. 往前#DAYS/2个周期、往后#DAYS/2个周期价格都比它低
		 */
		
		// 为空则查所有数据
		if (list == null) {
			list = stockDao.findByCode(code);
		}
		// 先放入map中, key=时间，value=stock对象
		List<Dot> result = new ArrayList<Dot>();
		Map<String, Stock> dateMap = new HashMap<String, Stock>();
		for (Stock stock : list) {
			dateMap.put(stock.getDate(), stock);
		}
		// 往前#DAYS/2天， 往后#DAYS/2天的推算
		for (Stock stock : list) {
			String date = stock.getDate();
			
			// 得到前后10天的股票对象
			List<Stock> toCompareList = new ArrayList<Stock>();
			for (int i = 1; i <= DAYS/2; i++) {
				String compareBeforeDate = DateUtil.addDays(date, i, "yyyyMMdd");
				String compareAfterDate = DateUtil.addDays(date, -i, "yyyyMMdd");
				
				Stock beforeStock = dateMap.get(compareBeforeDate);
				if (beforeStock != null) {
					toCompareList.add(beforeStock);
				}
				Stock afterStock = dateMap.get(compareAfterDate);
				if (afterStock != null) {
					toCompareList.add(afterStock);
				}
			}
			
			// 比较价格
			boolean high = true;
			for (Stock compareStock : toCompareList) {
				if (stock.getHigh().doubleValue() < compareStock.getHigh().doubleValue()) {
					high = false;
					break;
				}
			}
			if (high) {
				Dot dot = new Dot();
				dot.setType(Dot.Type_High);
				dot.setCode(stock.getCode());
				dot.setPrice(stock.getHigh());
				dot.setDate(stock.getDate());
				
				result.add(dot);
			}
		}
		return result;
	}
	
	public static void main(String[] args) {
		DotService stockService = new DotService();
		List<Dot> lowList = stockService.getAllHighLow("999999", null);
		
		System.out.println("total:" + lowList.size());
		for (Dot dot : lowList) {
			System.out.println(dot);
		}
	}
	
}
